package com.wemei.auto

import android.app.AlertDialog
import android.app.Notification
import android.app.NotificationChannel
import android.app.NotificationManager
import android.app.PendingIntent
import android.content.Context
import android.content.Intent
import android.graphics.Color
import android.os.Build
import android.util.Log
import android.view.Gravity
import android.view.View
import android.view.WindowManager
import android.view.accessibility.AccessibilityEvent
import android.view.accessibility.AccessibilityNodeInfo
import android.widget.TextView
import android.widget.Toast
import androidx.core.app.NotificationCompat
import com.alibaba.fastjson.JSON
import com.lzf.easyfloat.EasyFloat
import com.lzf.easyfloat.enums.ShowPattern
import com.lzf.easyfloat.enums.SidePattern
import com.tencent.bugly.crashreport.CrashReport
import com.wemei.auto.api.core.FirmException
import com.wemei.auto.api.core.globalLaunchUI
import com.wemei.auto.cp_fast_accessibility.AnalyzeSourceResult
import com.wemei.auto.cp_fast_accessibility.EventWrapper
import com.wemei.auto.cp_fast_accessibility.FastAccessibilityService
import com.wemei.auto.cp_fast_accessibility.NodeWrapper
import com.wemei.auto.cp_fast_accessibility.back
import com.wemei.auto.cp_fast_accessibility.click
import com.wemei.auto.cp_fast_accessibility.findAllNode
import com.wemei.auto.cp_fast_accessibility.findNodeByExpression
import com.wemei.auto.cp_fast_accessibility.findNodeByExpressionNext
import com.wemei.auto.cp_fast_accessibility.findNodeById
import com.wemei.auto.cp_fast_accessibility.findNodeByText
import com.wemei.auto.cp_fast_accessibility.findNodesByIdNext
import com.wemei.auto.cp_fast_accessibility.input
import com.wemei.auto.cp_fast_accessibility.scrollForward
import com.wemei.auto.ui.ext.dp
import com.wemei.auto.ui.ext.drawable
import com.wemei.auto.ui.ext.format
import com.wemei.auto.ui.ext.toColor
import com.wemei.auto.ui.utils.Logger
import com.wemei.auto.ui.utils.SPUtils
import kotlinx.coroutines.CoroutineExceptionHandler
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.Job
import kotlinx.coroutines.delay
import kotlinx.coroutines.isActive
import kotlinx.coroutines.launch
import kotlinx.coroutines.suspendCancellableCoroutine
import kotlinx.coroutines.withContext
import java.util.Date
import kotlin.coroutines.resume
import kotlin.coroutines.resumeWithException
import kotlin.random.Random


/**
 * Author: CoderPig
 * Date: 2023-03-24
 * Desc:
 */
class MyAccessibilityService : FastAccessibilityService() {
    companion object {
        private const val TAG = "CpFastAccessibility"
        const val CHANNEL_ID: String = "无障碍服务"
        const val NOTIFICATION_ID: Int = 1
        val COMMENT_MAX_PAGE: Int = if (BuildConfig.DEBUG) 3 else 10
        var instance: MyAccessibilityService? = null
    }

    override val enableListenApp = true
    private var foregroundNotification: Notification? = null
    private var buttonEnd: TextView? = null
    private var buttonStart: TextView? = null
    private var startStatus: Boolean = false

    override fun onServiceConnected() {
        super.onServiceConnected()
        Log.e("CpFastAccessibility", "启动服务")
        Log.e(TAG, "onServiceConnected")
        instance = this
        showForegroundNotification("青鸾数字", "守护进程", "提示信息", activityClass = MainActivity::class.java)
        showFloatWindow()
    }

    override fun onDestroy() {
        super.onDestroy()
        instance = null
        closeForegroundNotification()
        dismissFloatWindow()
        end(false)
        buttonEnd = null
        buttonStart = null
    }

    private var checkPackageName = "com.ss.android.ugc.aweme"
    private var appName = "抖音"

    private suspend fun suspendAnalyzeSource(): AnalyzeSourceResult {
        return super.suspendAnalyzeSource(checkPackageName, appName)
    }

    override fun getRootInActiveWindow(): AccessibilityNodeInfo? {
        return windows?.find { it.title == appName }?.root ?: super.getRootInActiveWindow()
    }

    private fun testCode() {
        globalLaunchUI({
            var result: AnalyzeSourceResult? = suspendAnalyzeSource()
            result?.nodes?.forEach {
                Logger.e(it.toString())
            }
            val dyUsers = userComment(result)
            floatLog("读取到评论：${dyUsers.size}")
            floatLog("第一个用户点击：${dyUsers.firstOrNull()?.avatarNode}")
            dyUsers.firstOrNull()?.avatarNode?.click()
            delay(4000)
            val xb = SPUtils.getString("user_tag1")
            val sf = SPUtils.getString("user_tag2")
            execSxGz(xb, sf)
        })
    }

    private var job: Job? = null
    private fun start() {
//        if (BuildConfig.DEBUG) {
//            testCode()
//            return
//        }

        if (checkExpiration()) {
            Toast.makeText(appContext, "使用已到期，请联系管理员。", Toast.LENGTH_LONG).show()
            return
        }
        if (!recordGz()) {
            Toast.makeText(appContext, "已超过最大关注数量，停止运行", Toast.LENGTH_LONG).show()
            return
        }
        if ((job != null && job?.isActive == true) || startStatus) {
            Toast.makeText(appContext, "任务进行中，如需重新开始请先点击结束", Toast.LENGTH_LONG).show()
            return
        }
        val exceptionHandler = CoroutineExceptionHandler { _, throwable ->
            Log.e(TAG, "异常", throwable)
            if (throwable is FirmException) {
                floatLog(throwable.message)
            } else {
                floatLog("程序运行异常，已停止")
            }
            end()
            CrashReport.postCatchedException(throwable)
        }
        changeStartStatus(true)
        job = GlobalScope.launch(exceptionHandler) {
            showAlert()
            val texts = JSON.parseArray(SPUtils.getString("texts", "[]"), String::class.java)
            val jetexts = JSON.parseArray(SPUtils.getString("jetexts", "[]"), String::class.java)
            val xb = SPUtils.getString("user_tag1")
            val sf = SPUtils.getString("user_tag2")
            floatLog("本次运评价关键字：${JSON.toJSONString(texts)}")
            floatLog("本次运行简介关键字：${JSON.toJSONString(jetexts)}")
            mainLoop@ while (isActive) {
                if (checkExpiration()) {
                    end(false)
                    break
                }
                var result: AnalyzeSourceResult? = suspendAnalyzeSource()
                // 输出视频相关信息
                val videTitle = result?.findNodeByExpression {
                    it.id == "com.ss.android.ugc.aweme:id/title" && it.clickable && it.nodeInfo?.isVisibleToUser == true
                }
                val videDesc = result?.findNodeByExpression {
                    it.id == "com.ss.android.ugc.aweme:id/desc" && it.nodeInfo?.isVisibleToUser == true
                }
                val zbj = result?.findNodeByExpression {
                    it.description == "点击进入直播间按钮" && it.clickable && it.nodeInfo?.isVisibleToUser == true
                }
                floatLog(if (videTitle != null) "作者：${videTitle.text}" else null)
                floatLog(if (videDesc != null) "描述：${videDesc.text}" else null)
                floatLog(if (zbj != null) "直播：${zbj?.description}" else null)
                if (zbj != null || videTitle == null || videDesc == null || videDesc.text?.endsWith("广告") == true) {
                    delay(2000)
                    scrollVideoForward(result)
                    delay(2000)
                    continue
                }
                if (jetexts.any { videDesc.text?.contains(it) == true || videTitle.text?.contains(it) == true }) {
                    // 是否触发点赞。私信
                    val cbCurVideoDz = SPUtils.getBoolean("curVideoDz", false)
                    val cbCurVideoSx = SPUtils.getBoolean("curVideoSx", false)
                    if (cbCurVideoDz) {
                        val dz = result?.findNodesByIdNext("com.ss.android.ugc.aweme:id/user_avatar", isVisibleToUser = true) { index, node ->
                            node.description?.contains("点赞") == true
                        }
                        if (dz?.description?.contains("未点赞") == true) {
                            Logger.e("未点赞")
                            dz.click()
                            delay(2000)
                        }
                    }
                    if (cbCurVideoSx) {
                        val user_avatar =
                            result?.findNodeById("com.ss.android.ugc.aweme:id/user_avatar") { node -> node.nodeInfo?.isVisibleToUser == true }
                        // 广告不进入
                        val guanggao = result?.findNodeByExpression { node ->
                            node.className == "com.lynx.tasm.behavior.ui.text.FlattenUIText" && node.text == "广告" && node.description == "广告"
                                    && node.nodeInfo?.isVisibleToUser == true
                        }
                        if (guanggao == null) {
                            user_avatar?.click()
                            delay(4000)
                            // 执行私信点赞
                            execSxGz(xb, sf)
                            delay(2000)
                        }
                    }

                    //触发点击查看评论
                    var commentContainer: NodeWrapper?
                    var errorCut = 0
                    outerLoop@ while (true) {
                        result = suspendAnalyzeSource()
                        commentContainer =
                            result.findNodeById("com.ss.android.ugc.aweme:id/comment_container") { it.nodeInfo?.isVisibleToUser == true }
                        if (commentContainer == null) {
                            delay(2000)
                            floatLog("未获取到视频页面评论按钮==>${errorCut}")
                            // 统计次数超过多少次基本上是读取异常了退出任务或者重新开始
                            errorCut++
                            if (errorCut > 2) {
                                break@outerLoop
                            }
                        } else {
                            break@outerLoop
                        }
                    }
                    if (commentContainer == null) {
                        floatLog("或获取到频率按钮下一个")
                        result = suspendAnalyzeSource()
                        scrollVideoForward(result)
                        delay(2000)
                    } else {
                        val commentCut =
                            result?.findNodeByExpressionNext({
                                it.id == "com.ss.android.ugc.aweme:id/comment_container" && it.nodeInfo?.isVisibleToUser == true
                            }) { index: Int, node: NodeWrapper ->
                                index == 2 && node.className == "android.widget.TextView"
                            }
                        if (commentCut?.text == "评论") {
                            delay(2000)
                            scrollVideoForward(result)
                            continue
                        }
                        floatLog("获取到视频页面评论按钮点击打开评论页面")
                        // 点击评论
                        commentContainer.click()
                        delay(4000)
                        // 输入法弹出来了说明没有评论直接返回视频页
//                        if (isInputMethodShown()) {
//                            back()
//                            delay(2000)
//                            back()
//                            delay(2000)
//                            continue
//                        }
                        // 评论只读取10页
                        for (i in 1..COMMENT_MAX_PAGE) {
                            if (!isActive) {
                                break
                            }
                            if (checkExpiration()) {
                                end(false)
                                break@mainLoop
                            }
                            // 读取评论
                            result = suspendAnalyzeSource()
                            val wdl = result.findNodeByText("登录看更多精彩评论", includeDesc = true)
                            if (wdl != null) {
                                throw FirmException("当前[${appName}],未登录账号，程序停止")
                            }
                            val dyUsers = userComment(result)
                            floatLog("读取到评论：${dyUsers.size}")
                            dyUsers.forEach { floatLog("读取到用户：${JSON.toJSONString(it)}") }
                            if (dyUsers.isNotEmpty()) {
                                for (dyUser in dyUsers) {
                                    if (texts.any { dyUser.content?.contains(it) == true } && dyUser.content?.endsWith(" 详情") == false) {
                                        floatLog("评论命中关键字：${JSON.toJSONString(dyUser)}")
                                        delay(2000)
                                        dyUser.avatarNode?.click()
                                        delay(4000)
                                        if (isInputMethodShown()) {
                                            back()
                                            delay(2000)
                                            continue
                                        }
                                        execSxGz(xb, sf)
                                    }
                                }
                            }
                            floatLog("当前页${i},处理完毕上滑一页${JSON.toJSONString(dyUsers)}")
                            delay(2000)
                            result = suspendAnalyzeSource()
                            val zsmygdNode = result?.findNodeByText("暂时没有更多了", includeDesc = true)
                            if (zsmygdNode != null) {
                                break
                            }
                            // 滑动评论
                            scrollCommentForward(result)
                            delay(3000)
                        }
                        floatLog("当前视频评论处理完返回视频页滑动加载下一个视频")
                        delay(2000)
                        back()
                        delay(2000)
                        result = suspendAnalyzeSource()
                        scrollVideoForward(result)
                        delay(2000)
                    }
                } else {
                    delay(2000)
                    result = suspendAnalyzeSource()
                    scrollVideoForward(result)
                    delay(2000)
                }
            }
        }
    }

    private suspend fun execSxGz(xb: String, sf: String) {
        var result = suspendAnalyzeSource()
        var xbfx = xb.isBlank()
        var sffx = sf.isBlank()
        Logger.e("本次获目标性别：${xb}")
        if (xb.isNotBlank() || sf.isNotBlank()) {
            val xbnan = result.findNodeByExpression { it.description?.startsWith("男") == true }
            val xbnv = result.findNodeByExpression { it.description?.startsWith("女") == true }
            Logger.e("本次获取到性别：${xbnan?.description ?: xbnv?.description}")
            if (xbnan?.description?.contains(xb) == true || xbnv?.description?.contains(xb) == true) {
                xbfx = true
            }
        }
        Logger.e("性别过滤结果：${xbfx}")

        Logger.e("本次获目标省份：${sf}")
        if (xb.isNotBlank() || sf.isNotBlank()) {
            val ip = result.findNodeByText("IP", includeDesc = true)
            Logger.e("本次获取到省份：${ip}")
            if (ip?.text?.contains(sf) == true) {
                sffx = true
            }
        }
        Logger.e("省份过滤结果：${sffx}")
        delay(2000)
        // 若没有命中关键字或者私信上限不发送私信
        if (!xbfx || !sffx || !recordSx()) {
            back()
            delay(2000)
            return
        }

        // 第一条作品点赞
        val zwgdzp = result.findNodeByText("暂无作品")
        val smzh = result.findNodeByText("私密账号")
        if (zwgdzp == null && smzh == null) {
            result.findNodesByIdNext("com.ss.android.ugc.aweme:id/container") { index, node ->
                index == 0
            }?.let { container ->
                runCatching {
                    container.click()
                    delay(4000)
                    result = suspendAnalyzeSource()
                    val dz = result.findNodesByIdNext("com.ss.android.ugc.aweme:id/user_avatar") { index, node ->
                        node.description?.contains("点赞") == true
                    }
                    // 未点赞
                    Logger.e("dz==>${dz}")
                    if (dz?.description?.contains("未点赞") == true) {
                        dz.click()
                    }
                    delay(2000)
                    if (dz != null) {
                        back()
                    }
                }
            }
        }

        result = suspendAnalyzeSource()
        // 如果没有关注点击关注
        val wyz = result.findNodeByText("关注", true, click = true)
        // 没关注先点击关注
        if (wyz != null) {
            floatLog("没有关注触发关注")
            wyz.click()
            if (!recordGz(true)) {
                throw FirmException("已超过最大关注数量，停止运行")
            }
            delay(3000)
            result = suspendAnalyzeSource()
            val qr = result.findNodeByExpression {
                it.id == "com.ss.android.ugc.aweme:id/qr"
                        && it.text == "确认" && it.clickable
            }
            if (qr != null) {
                floatLog("出现确认页面，点击确认")
                qr.click()
                delay(2000)
            }
        }
        delay(1000)

        floatLog("点击私信")
        // 点击发送私信进入私信页面
        result = suspendAnalyzeSource()
        val sx = result?.findNodeByText("私信", true, click = true)
        if (sx == null) {
            // 私信按钮没找到可能页面出问题了，返回吧
            if (isInputMethodShown()) {
                back()
                delay(2000)
                back()
                delay(2000)
            } else {
                delay(2000)
                back()
                delay(2000)
            }
        } else {
            sx?.click()
            delay(4000)
            // 判断是否发送过私信，发送过不要在发送
            val sx_centent = SPUtils.getString("sx_centent")
            floatLog("本次发送私信文本：${sx_centent}")
            if (sx_centent.isNotBlank()) {
                result = suspendAnalyzeSource()
                val sxText =
                    result?.findNodeByExpression {
                        it.id == "com.ss.android.ugc.aweme:id/content_layout"
                                && it.className == "android.widget.TextView"
                                && it.text == sx_centent
                    }
                if (sxText == null) {
                    floatLog("未发送过私信触发发送")
                    result?.findNodeById("com.ss.android.ugc.aweme:id/msg_et")?.input(sx_centent)
                    delay(2000)
                    result = suspendAnalyzeSource()
                    val fs = result?.findNodeByText("发送", includeDesc = true, descAllMatch = true, click = true)
                    Logger.e("")
                    fs?.click()
                    delay(3000)
                    recordSx(true)
                }
            }
            floatLog("结束私信页面返回两层到评论页面")
            // 返回两层，1次返回用户详情，2次返回到评论页
            back()
            delay(2000)
            back()
        }
    }

    private fun scrollCommentForward(result: AnalyzeSourceResult?) {
        var comment = result?.findNodesByIdNext("com.ss.android.ugc.aweme:id/title", "条评论") { index: Int, node: NodeWrapper ->
            index == 1
        }
        if (comment == null) {
            comment = result?.findNodeByExpression { it.className == "androidx.recyclerview.widget.RecyclerView" && it.scrollable }
        }
        comment?.scrollForward()
    }

    private fun scrollVideoForward(result: AnalyzeSourceResult?) {
        var viewpager = result?.findNodeByExpression {
            it.id == "com.ss.android.ugc.aweme:id/viewpager" && it.scrollable && it.description == "视频" && it.nodeInfo?.isVisibleToUser == true
        }
        if (viewpager == null) {
            viewpager =
                result?.findNodeByExpression { it.id == "com.ss.android.ugc.aweme:id/viewpager" && it.className == "androidx.viewpager.widget.ViewPager" && it.scrollable }
        }
        viewpager?.scrollForward()
    }

    private fun recordSx(addCut: Boolean = true): Boolean {
        var sx_day = SPUtils.getString("sx_day")
        Logger.e("本次获取日期：${sx_day}")
        val current = Date().format()
        if (sx_day != current) {
            SPUtils.remove("sx_day_$sx_day")
            sx_day = current
            SPUtils.put("sx_day", sx_day)
        }
        var sx_max_centent = SPUtils.getString("sx_max_centent", "25").toInt()
        if (sx_max_centent > 25) {
            sx_max_centent = 25
        }
        Logger.e("本次获取最大私信次数${sx_max_centent}")
        val sx_day_cut = SPUtils.getInt("sx_day_$sx_day", 0)
        Logger.e("本次获取日期对应私信天数：${sx_day_cut}")
        if (sx_day_cut + 1 > sx_max_centent) {
            return false
        }
        if (addCut) {
            SPUtils.put("sx_day_$sx_day", sx_day_cut + 1)
        }
        return true
    }

    private fun recordGz(addCut: Boolean = true): Boolean {
        var gz_day = SPUtils.getString("gz_day")
        Logger.e("本次获取日期：${gz_day}")
        val current = Date().format()
        if (gz_day != current) {
            SPUtils.remove("gz_day_$gz_day")
            gz_day = current
            SPUtils.put("gz_day", gz_day)
            SPUtils.put("gz_max_centent", 90 + Random.nextInt(20))
        }

        val gz_max_centent = SPUtils.getInt("gz_max_centent", 99)
        Logger.e("本次获取日期对应关注最大天数：${gz_max_centent}")
        val gz_day_cut = SPUtils.getInt("gz_day_$gz_day", 0)
        Logger.e("本次获取日期对应关注天数：${gz_day_cut}")
        if (gz_day_cut + 1 > gz_max_centent) {
            return false
        }
        if (addCut) {
            SPUtils.put("gz_day_$gz_day", gz_day_cut + 1)
        }
        return true
    }

    fun end(toast: Boolean = true) {
        changeStartStatus(false)
        if (job?.isActive == true) {
            job?.cancel()
            job = null
        }
        if (toast) {
            //Toast.makeText(appContext, "取消成功，如需重新开始期待5秒钟", Toast.LENGTH_LONG).show()
        }
    }

    private var lastText: String? = null

    private fun floatLog(text: String?) {
        if (text == null) {
            return
        }
        Log.e(TAG, text)
//        tvLog?.post { tvLog?.text = "${lastText ?: ""}\n${text}" }
        lastText = text
    }

    private suspend fun showAlert() {
        withContext(Dispatchers.Main) {
            suspendCancellableCoroutine { coroutine ->
                val mDialog = AlertDialog.Builder(this@MyAccessibilityService, android.R.style.Theme_DeviceDefault_Light_Dialog)
                    .setCancelable(false)
                    .setTitle("温馨提示")
                    .setMessage(
                        "1、请确定当前页面是：${appName}首页，否则无法运行。" +
                                "\n2、功能区一定要给最下面留出空间否则无法私信。\n" +
                                "3、程序运行时请不要再操作手机，否则程序可能会异常中断。"
                    )
                    .setNegativeButton("取消") { _, _ ->
                        coroutine.resumeWithException(FirmException("点击取消,程序停止"))
                    }
                    .setPositiveButton("确定") { _, _ ->
                        coroutine.resume("")
                    }
                    .create()
                // 关键：设置窗口类型为无障碍覆盖层
                if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
                    mDialog.window?.setType(WindowManager.LayoutParams.TYPE_ACCESSIBILITY_OVERLAY);
                } else {
                    mDialog.window?.setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
                }
                // 添加标志位确保显示在其他应用上方
                mDialog.window?.addFlags(
                    WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE or
                            WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL or
                            WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
                )
                mDialog.show()
            }
        }
    }

    override fun analyzeCallBack(wrapper: EventWrapper?, result: AnalyzeSourceResult) {
//  result.findNodeByText("搜索").click()
        //
        Log.e(TAG, "===>${result.nodes.firstOrNull()?.packageName}")
        Log.e(TAG, "触发无障碍")
        result.findAllNode().nodes.forEach { Log.e(TAG, "${it.id}<===>${it.clickable}<==>${it.className}=${it.text}<===>${it.description}") }
//        result.findNodesByIdNext("com.ss.android.ugc.aweme:id/viewpager") { index: Int, node: NodeWrapper -> index == 1 }?.scrollForward()

        val viewpager = result.findNodeByExpression {
            it.id == "com.ss.android.ugc.aweme:id/viewpager" && it.scrollable && it.description == "视频" && it.nodeInfo?.isVisibleToUser == true
        }
        Log.e(TAG, "ccccccccccccc${viewpager != null}")
//        viewpager?.scrollForward()
        val videTitle = result.findNodeByExpression {
            it.id == "com.ss.android.ugc.aweme:id/title" && it.clickable && it.nodeInfo?.isVisibleToUser == true
        }
        val videDesc = result.findNodeByExpression {
            it.id == "com.ss.android.ugc.aweme:id/desc" && it.nodeInfo?.isVisibleToUser == true
        }
        val zbj = result.findNodeByExpression {
            it.description == "点击进入直播间按钮" && it.clickable && it.nodeInfo?.isVisibleToUser == true
        }
        Log.e(TAG, "${videTitle?.text}")
        Log.e(TAG, "${videDesc?.text}")
        Log.e(TAG, "${zbj?.description}")
//        result.findNodesById("com.ss.android.ugc.aweme:id/desc").nodes
//            .forEach {
//                Log.e(
//                    TAG,
//                    "${it.nodeInfo?.isVisibleToUser}<----->${it.id}<=1111111111==>${it.clickable}<==>${it.className}=${it.text}<===>${it.description}"
//                )
//            }

        // 首页滑动视频
//        val screenSize = getRealScreenSize(this)
//        val startX = screenSize.x / 2
//        val height = screenSize.y / 4
//        Log.e(TAG, "${startX}<===>${screenSize.x / 5 * 4} <==>${screenSize.x / 5}")
//        swipe(screenSize.x / 2, screenSize.x / 5 * 4, screenSize.x / 2, screenSize.x / 5,300)

        // 触发点击查看评论
//        result.findNodeById("com.ss.android.ugc.aweme:id/comment_container") { it.nodeInfo?.isVisibleToUser == true }?.click()

        // 滑动评论
//        result.findNodesByIdNext("com.ss.android.ugc.aweme:id/title","条评论") { index: Int, node: NodeWrapper ->
//            index == 1
//        }?.scrollForward()

        // 去读评论，并点击头像
//        userComment(result)

        // 如果没有关注点击关注
        val ygz = result.findNodeByText("已关注", true, click = true)
        val wyz = result.findNodeByText("关注", true, click = true)
        val sx = result.findNodeByText("私信", true, click = true)
        Log.e(TAG, "===》${ygz != null}")
        Log.e(TAG, "===》${wyz != null}")
        Log.e(TAG, "===》${sx != null}")
//        result.findNodeByText("关注", true, click = true)?.click()
        val qr = result.findNodeByExpression { it.id == "com.ss.android.ugc.aweme:id/qr" && it.text == "确认" && it.clickable }

        Log.e(TAG, "qr===》${qr != null}")
//        sx?.click()
        // 点击发送私信进入私信页面
//        result.findNodeById("com.ss.android.ugc.aweme:id/msg_et")?.input("周六出去玩")
        // 判断是否发送过私信，发送过不要在发送
//        result.findNodeByText("发送", includeDesc = true, descAllMatch = true, click = true)?.click()

        val text =
            result.findNodeByExpression { it.id == "com.ss.android.ugc.aweme:id/content_layout" && it.className == "android.widget.TextView" }?.text
        Log.e(TAG, "text===》${text}")
        // 结束，回到评论页面

//        back()
    }

    private fun userComment(result: AnalyzeSourceResult?): MutableList<DyUser> {
        if (result == null) {
            return mutableListOf()
        }
        val id = "com.ss.android.ugc.aweme:id/title"
        val startComment = "条评论"
        var index = 0
        var startFlag = false
        var userStartFlag = false
        val dyUsers = mutableListOf<DyUser>()
        var mDyUser: DyUser? = null
        for (node in result.nodes) {
            if (startFlag) {
                if (!userStartFlag && node.id == "com.ss.android.ugc.aweme:id/avatar") {
                    userStartFlag = true
                    mDyUser = DyUser()
                    dyUsers.add(mDyUser)
                    mDyUser.avatarNode = node
                    mDyUser.avatar = node.text?.ifBlank { node.description }
                }
                if (userStartFlag && node.id == "com.ss.android.ugc.aweme:id/title") {
                    mDyUser?.title = node.text?.ifBlank { node.description }
                }
                if (userStartFlag && node.id == "com.ss.android.ugc.aweme:id/content") {
                    userStartFlag = false
                    mDyUser?.content = node.text?.ifBlank { node.description }
                }
            }
            if (startFlag) {
                index++
            }
            if (!node.id.isNullOrBlank()) {
                if (node.id!!.contains(id) && node.text?.contains(startComment) == true) {
                    startFlag = true
                }
                if (node.text?.startsWith("评论") == true) {
                    val cut = node.text?.split(" ")?.lastOrNull()?.toIntOrNull()
                    if (cut != null) {
                        startFlag = true
                    }
                }
            }
        }
        return dyUsers
    }

    private fun showForegroundNotification(
        title: String = "通知标题",
        content: String = "通知内容",
        ticker: String = "通知提示语",
        iconRes: Int = R.mipmap.ic_launcher,
        activityClass: Class<*>? = null
    ) {
        val context = instance
        Log.e("CpFastAccessibility", "context=>$context")
        val channelName = "前台服务通知" // 定义渠道名称

        // 创建通知渠道
        val notificationManager = instance?.getSystemService(Context.NOTIFICATION_SERVICE) as NotificationManager
        Log.e("CpFastAccessibility", "notificationManager--${notificationManager}")
        Log.e("CpFastAccessibility", "notificationManager--${notificationManager.areNotificationsEnabled()}")
        val channel = NotificationChannel(
            CHANNEL_ID,
            channelName,
            NotificationManager.IMPORTANCE_HIGH // 修正常量名
        ).apply {
            enableLights(true)          // 开启指示灯
            lightColor = Color.BLUE     // 设置指示灯颜色
            enableVibration(true)       // 开启震动
            vibrationPattern = longArrayOf(100, 200, 300, 400) // 修正数组类型
            setShowBadge(true)          // 显示角标
            setBypassDnd(true)
            lockscreenVisibility = Notification.VISIBILITY_PRIVATE // 锁屏可见性
        }
        notificationManager.createNotificationChannel(channel)

        // 构建通知
        foregroundNotification = NotificationCompat.Builder(appContext, CHANNEL_ID).apply {
            setSmallIcon(iconRes)
            setContentTitle(title)
            setContentText(content)
            setTicker(ticker)
            priority = NotificationCompat.PRIORITY_MIN // 设置低优先级

            // 添加点击跳转
            activityClass?.let {
                val intent = Intent(context, it)
                val pendingIntent = PendingIntent.getActivity(
                    context,
                    0,
                    intent,
                    PendingIntent.FLAG_IMMUTABLE // 修正标志名
                )
                setContentIntent(pendingIntent)
            }
        }.build()

        Log.e("CpFastAccessibility", "启动前台服务")
        // 启动前台服务
        startForeground(NOTIFICATION_ID, foregroundNotification) // 需要唯一通知ID
    }

    private fun closeForegroundNotification() {
        foregroundNotification?.let { stopForeground(true) }
    }

    private fun startTest() {
        FastAccessibilityService.onAnalyzeSource(AccessibilityEvent.obtain(AccessibilityEvent.TYPE_VIEW_CLICKED).apply {
            className = "android.widget.FrameLayout"
            packageName = BuildConfig.APPLICATION_ID
        })
    }

    fun showFloatWindow() {
        if (!EasyFloat.isShow("MyAccessibilityService")) {
            EasyFloat.with(this)
                .setLayout(R.layout.layout_float_window) {
                    buttonStart = it.findViewById(R.id.button_start)
                    buttonStart?.setOnClickListener {
                        start()
                    }
                    buttonEnd = it.findViewById(R.id.button_end)
                    buttonEnd?.setOnClickListener {
                        end()
                    }
                }
                .setShowPattern(ShowPattern.ALL_TIME)
                .setSidePattern(SidePattern.RESULT_RIGHT)
                .setTag("MyAccessibilityService")
                .setGravity(Gravity.BOTTOM or Gravity.RIGHT, 0, -(50.dp))
                .setLayoutChangedGravity(Gravity.END)
                .setMatchParent(widthMatch = false, heightMatch = false)
                .show()
        }
    }

    private fun changeStartStatus(start: Boolean) {
        startStatus = start
        if (startStatus) {
            buttonEnd?.background = R.drawable.bg_main_radius_5.drawable
            buttonEnd?.setTextColor(R.color.white.toColor())

            buttonStart?.background = R.drawable.bg_main_gray_radius_6.drawable
            buttonStart?.setTextColor(R.color.text_hint_color_2.toColor())
        } else {
            buttonStart?.background = R.drawable.bg_main_radius_5.drawable
            buttonStart?.setTextColor(R.color.white.toColor())

            buttonEnd?.background = R.drawable.bg_main_gray_radius_6.drawable
            buttonEnd?.setTextColor(R.color.text_hint_color_2.toColor())
        }
    }

    private fun dismissFloatWindow() {
        EasyFloat.dismiss("MyAccessibilityService")
    }
}